
import config
import app.tools as tool
from PyQt4.QtCore import Qt as CoreQt
from PyQt4 import QtCore, QtGui, Qt
from app.ui import Icon
from app.tools.table import TableWidget, TableWidgetItem
from lib.redis import RedisFacotry
from lib.tools.type import RedisConnectType, ConnectTabIndex
from lib.storage import Storage



class ConnectWindow(QtGui.QDialog):

    def __init__(self, parent=None):
        super(ConnectWindow, self).__init__(parent)
        self.icon = Icon()
        self.parent = parent
        self.logger = parent.logger
        self.init_ui()

    def init_style(self):
        style = QtCore.QString(open(config.RESOURCE_STYLE_SHEET).read())
        self.setStyleSheet(style)

    def init_ui(self):
        self.setWindowTitle(tool._from_utf8('ConnectWindow'))
        self.setObjectName(tool._from_utf8("ConnectWindow"))
        parent_geometry = self.parent.geometry()
        parent_width = parent_geometry.width()
        parent_height = parent_geometry.height()
        current_width = parent_width * 0.8
        current_height = parent_height * 0.8
        current_left = parent_geometry.left() + (parent_width - current_width) / 2
        current_top = parent_geometry.top() + (parent_height - current_height) / 2
        current_rect = QtCore.QRect(current_left, current_top, current_width, current_height)
        self.setGeometry(current_rect)

        self.vertical_layout_widget = QtGui.QWidget(self)
        # self.vertical_layout_widget.setGeometry(QtCore.QRect(0, 0, 531, 321))
        parent_rect = QtCore.QRect(0, 0, current_width, current_height)
        self.vertical_layout_widget.setGeometry(parent_rect)
        self.vertical_layout_widget.setObjectName(tool._from_utf8("vertical_layout_widget"))
        self.vertical_layout = QtGui.QVBoxLayout(self.vertical_layout_widget)
        self.vertical_layout.setObjectName(tool._from_utf8("vertical_layout"))

        self.tab_widget = QtGui.QTabWidget(self.vertical_layout_widget)
        self.tab_widget.setObjectName(tool._from_utf8("tab_widget"))

        self.tab_client = QtGui.QWidget()
        self.tab_client.setObjectName(tool._from_utf8("tab_client"))
        self.client_form_layout_widget = QtGui.QWidget(self.tab_client)

        client_form_layout_widget_rect = QtCore.QRect(20, 20, current_width - (current_width * 0.1), current_height)
        self.client_form_layout_widget.setGeometry(client_form_layout_widget_rect)
        self.client_form_layout_widget.setObjectName(tool._from_utf8("client_form_layout_widget"))

        self.form_layout_client = QtGui.QFormLayout(self.client_form_layout_widget)
        self.form_layout_client.setObjectName(tool._from_utf8("form_layout_client"))

        self.client_name_label = QtGui.QLabel(self.client_form_layout_widget)
        self.client_name_label.setObjectName(tool._from_utf8("client_name_label"))
        self.client_name_label.setText(tool._from_utf8('Name: '))
        self.form_layout_client.setWidget(0, QtGui.QFormLayout.LabelRole, self.client_name_label)

        self.client_name_line_edit = QtGui.QLineEdit(self.client_form_layout_widget)
        self.client_name_line_edit.setObjectName(tool._from_utf8("client_name_line_edit"))
        self.form_layout_client.setWidget(0, QtGui.QFormLayout.FieldRole, self.client_name_line_edit)

        self.client_host_label = QtGui.QLabel(self.client_form_layout_widget)
        self.client_host_label.setObjectName(tool._from_utf8("client_host_label"))
        self.client_host_label.setText(tool._from_utf8('Host: '))
        self.form_layout_client.setWidget(1, QtGui.QFormLayout.LabelRole, self.client_host_label)

        self.client_host_line_edit = QtGui.QLineEdit(self.client_form_layout_widget)
        self.client_host_line_edit.setObjectName(tool._from_utf8("client_host_line_edit"))
        self.client_host_line_edit.setText(tool._from_utf8(config.REDIS_DEFAULT_HOST))
        self.form_layout_client.setWidget(1, QtGui.QFormLayout.FieldRole, self.client_host_line_edit)

        self.client_port_label = QtGui.QLabel(self.client_form_layout_widget)
        self.client_port_label.setObjectName(tool._from_utf8("client_port_label"))
        self.client_port_label.setText(tool._from_utf8('Port: '))
        self.form_layout_client.setWidget(2, QtGui.QFormLayout.LabelRole, self.client_port_label)

        self.client_port_line_edit = QtGui.QLineEdit(self.client_form_layout_widget)
        self.client_port_line_edit.setObjectName(tool._from_utf8("client_port_line_edit"))
        self.client_port_line_edit.setText(tool._from_utf8(config.REDIS_DEFAULT_PORT))
        self.form_layout_client.setWidget(2, QtGui.QFormLayout.FieldRole, self.client_port_line_edit)

        self.client_auth_label = QtGui.QLabel(self.client_form_layout_widget)
        self.client_auth_label.setObjectName(tool._from_utf8("client_auth_label"))
        self.client_auth_label.setText(tool._from_utf8('Auth: '))
        self.form_layout_client.setWidget(3, QtGui.QFormLayout.LabelRole, self.client_auth_label)

        self.client_auth_line_edit = QtGui.QLineEdit(self.client_form_layout_widget)
        self.client_auth_line_edit.setObjectName(tool._from_utf8("client_auth_line_edit"))
        self.client_auth_line_edit.setEchoMode(Qt.QLineEdit.Password)
        self.form_layout_client.setWidget(3, QtGui.QFormLayout.FieldRole, self.client_auth_line_edit)
        self.tab_widget.addTab(self.tab_client, self.icon.get(config.ICON_SERVER), tool._from_utf8("Client"))

        self.tab_cluster = QtGui.QWidget()
        self.tab_cluster.setObjectName(tool._from_utf8("tab_cluster"))

        self.cluster_form_layout_widget = QtGui.QWidget(self.tab_cluster)
        cluster_form_layout_widget_rect = QtCore.QRect(20, 20, current_width - (current_width * 0.1), current_height)
        self.cluster_form_layout_widget.setGeometry(cluster_form_layout_widget_rect)
        self.cluster_form_layout_widget.setObjectName(tool._from_utf8("formLayoutWidget"))

        self.form_layout_cluster = QtGui.QFormLayout(self.cluster_form_layout_widget)
        self.form_layout_cluster.setObjectName(tool._from_utf8("form_layout_cluster"))

        self.cluster_name_label = QtGui.QLabel(self.cluster_form_layout_widget)
        self.cluster_name_label.setObjectName(tool._from_utf8("cluster_name_label"))
        self.cluster_name_label.setText(tool._from_utf8('Name: '))
        self.form_layout_cluster.setWidget(0, QtGui.QFormLayout.LabelRole, self.cluster_name_label)

        self.cluster_name_line_edit = QtGui.QLineEdit(self.cluster_form_layout_widget)
        self.cluster_name_line_edit.setObjectName(tool._from_utf8("cluster_name_line_edit"))
        self.form_layout_cluster.setWidget(0, QtGui.QFormLayout.FieldRole, self.cluster_name_line_edit)

        self.cluster_node_label = QtGui.QLabel(self.cluster_form_layout_widget)
        self.cluster_node_label.setObjectName(tool._from_utf8("cluster_node_label"))
        self.cluster_node_label.setText(tool._from_utf8('Nodes: '))
        self.form_layout_cluster.setWidget(1, QtGui.QFormLayout.LabelRole, self.cluster_node_label)

        self.cluster_auth_label = QtGui.QLabel(self.cluster_form_layout_widget)
        self.cluster_auth_label.setObjectName(tool._from_utf8("cluster_auth_label"))
        self.cluster_auth_label.setText(tool._from_utf8('Auth: '))
        self.form_layout_cluster.setWidget(2, QtGui.QFormLayout.LabelRole, self.cluster_auth_label)

        self.cluster_auth_line_edit = QtGui.QLineEdit(self.cluster_form_layout_widget)
        self.cluster_auth_line_edit.setObjectName(tool._from_utf8("cluster_auth_line_edit"))
        self.cluster_auth_line_edit.setEchoMode(Qt.QLineEdit.Password)
        self.form_layout_cluster.setWidget(2, QtGui.QFormLayout.FieldRole, self.cluster_auth_line_edit)

        self.horizontal_layout = QtGui.QHBoxLayout()
        self.horizontal_layout.setObjectName(tool._from_utf8("horizontal_layout"))

        self.node_table = TableWidget(self.cluster_form_layout_widget)
        self.node_table.set_object_name('node_table')
        self.node_table.init_ui()
        self.node_table.set_column_count(2)
        self.node_table.set_column_width(0, 400)
        self.node_table.set_selection_mode(TableWidget.SingleSelection)
        self.node_table.set_selection_behavior(TableWidget.SelectRows)
        self.node_table.set_horizontal_header(0, 'Host', self.icon.get(config.ICON_SERVER))
        self.node_table.set_horizontal_header(1, 'Port', self.icon.get(config.ICON_UA))

        row_count = 6
        self.node_table.set_row_count(row_count)
        for i in range(row_count):
            self.node_table.set_item(i, 0, '10.168.2.39')
            self.node_table.set_item(i, 1, '700%d' % i)

        self.horizontal_layout.addWidget(self.node_table)

        self.horizontal_layout_node_table_control = QtGui.QVBoxLayout()
        self.horizontal_layout_node_table_control.setObjectName(tool._from_utf8("horizontal_layout_node_table_control"))

        self.node_table_add_row_button = QtGui.QPushButton(self.cluster_form_layout_widget)
        self.node_table_add_row_button.setObjectName(tool._from_utf8("node_table_add_row_button"))
        self.node_table_add_row_button.setIcon(self.icon.get(config.ICON_ADD))
        self.node_table_add_row_button.setText(tool._from_utf8('Add Host'))
        self.node_table_add_row_button.clicked.connect(self.on_node_table_add_row_clicked)
        self.horizontal_layout_node_table_control.addWidget(self.node_table_add_row_button)

        self.node_table_delete_row_button = QtGui.QPushButton(self.cluster_form_layout_widget)
        self.node_table_delete_row_button.setObjectName(tool._from_utf8("node_table_delete_row_button"))
        self.node_table_delete_row_button.setIcon(self.icon.get(config.ICON_DEL))
        self.node_table_delete_row_button.setText(tool._from_utf8('Delete Host'))
        self.node_table_delete_row_button.clicked.connect(self.on_node_table_delete_row_clicked)
        self.horizontal_layout_node_table_control.addWidget(self.node_table_delete_row_button)

        spacer_item_table_button = QtGui.QSpacerItem(20, 40, QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
        self.horizontal_layout_node_table_control.addItem(spacer_item_table_button)
        self.horizontal_layout.addLayout(self.horizontal_layout_node_table_control)
        self.form_layout_cluster.setLayout(1, QtGui.QFormLayout.FieldRole, self.horizontal_layout)
        self.tab_widget.addTab(self.tab_cluster, self.icon.get(config.ICON_CLUSTER), tool._from_utf8("Cluster"))

        self.vertical_layout.addWidget(self.tab_widget)
        self.horizontal_layout_bottom = QtGui.QHBoxLayout()
        self.horizontal_layout_bottom.setObjectName(tool._from_utf8("horizontal_layout_bottom"))
        spacer_item_global_left = QtGui.QSpacerItem(40, 20, QtGui.QSizePolicy.Expanding, QtGui.QSizePolicy.Minimum)
        self.horizontal_layout_bottom.addItem(spacer_item_global_left)

        self.exit_button = QtGui.QPushButton(self.vertical_layout_widget)
        self.exit_button.setObjectName(tool._from_utf8("exit_button"))
        self.exit_button.setIcon(self.icon.get(config.ICON_CLEAR))
        self.exit_button.setText(tool._from_utf8('Exit'))
        self.exit_button.clicked.connect(self.on_back_clicked)
        self.horizontal_layout_bottom.addWidget(self.exit_button)

        self.connect_test_button = QtGui.QPushButton(self.vertical_layout_widget)
        self.connect_test_button.setObjectName(tool._from_utf8("connect_test_button"))
        self.connect_test_button.setIcon(self.icon.get(config.ICON_OFFLINE))
        self.connect_test_button.setText(tool._from_utf8('Test Connect'))
        self.connect_test_button.clicked.connect(self.on_connect_test_clicked)
        self.horizontal_layout_bottom.addWidget(self.connect_test_button)

        self.connect_button = QtGui.QPushButton(self.vertical_layout_widget)
        self.connect_button.setObjectName(tool._from_utf8("connect_button"))
        self.connect_button.setIcon(self.icon.get(config.ICON_OFFLINE))
        self.connect_button.setText(tool._from_utf8('Save Connect'))
        self.connect_button.clicked.connect(self.on_connect_clicked)
        self.horizontal_layout_bottom.addWidget(self.connect_button)

        spacer_item_global_right = QtGui.QSpacerItem(40, 20, QtGui.QSizePolicy.Expanding, QtGui.QSizePolicy.Minimum)
        self.horizontal_layout_bottom.addItem(spacer_item_global_right)
        self.vertical_layout.addLayout(self.horizontal_layout_bottom)

        self.tab_widget.setCurrentIndex(0)

    def on_back_clicked(self):
        self.close()

    def on_connect_test_clicked(self):
        print('on_connect_test_clicked')
        node_tab_current_index = self.tab_widget.currentIndex()
        if node_tab_current_index == ConnectTabIndex.Client.value:
            name = tool.qstring_to_string(self.client_name_line_edit.text())
            host = tool.qstring_to_string(self.client_host_line_edit.text())
            port = tool.qstring_to_string(self.client_port_line_edit.text())
            auth = tool.qstring_to_string(self.client_auth_line_edit.text())
            self.factory = RedisFacotry.create_client(host, port, auth, 0, self.logger)
        elif node_tab_current_index == ConnectTabIndex.Cluster.value:
            name = tool.qstring_to_string(self.cluster_name_line_edit.text())
            nodes = list()
            row_count = self.node_table.row_count()
            for i in range(row_count):
                item_host = self.node_table.item(i, 0)
                item_port = self.node_table.item(i, 1)
                if not item_host or not item_port:
                    continue
                host = item_host.text()
                if not host or host.isEmpty() or host.isNull():
                    continue
                host = tool.qstring_to_string(host)
                port = item_port.text()
                port = tool.qstring_to_string(port)
                nodes.append((host, port))
            auth = tool.qstring_to_string(self.cluster_auth_line_edit.text())
            self.factory = RedisFacotry.create_cluster(nodes, auth, self.logger)
        else:
            raise Exception('connect window select tab page error!')
        try:
            self.factory.ping()
        except UnicodeDecodeError:
            self.logger.info('connect error!')

    def on_connect_clicked(self):
        print('on_connect_clicked')
        node_tab_current_index = self.tab_widget.currentIndex()
        if node_tab_current_index == ConnectTabIndex.Client.value:
            name = tool.qstring_to_string(self.client_name_line_edit.text())
            host = tool.qstring_to_string(self.client_host_line_edit.text())
            port = tool.qstring_to_string(self.client_port_line_edit.text())
            auth = tool.qstring_to_string(self.client_auth_line_edit.text())
            self.factory = RedisFacotry.create_client(host, port, auth, 0, self.logger)
            storage = Storage()
            storage.insert(name, node_tab_current_index, [(host, port)], auth)
        elif node_tab_current_index == ConnectTabIndex.Cluster.value:
            name = tool.qstring_to_string(self.cluster_name_line_edit.text())
            nodes = list()
            row_count = self.node_table.row_count()
            for i in range(row_count):
                item_host = self.node_table.item(i, 0)
                item_port = self.node_table.item(i, 1)
                if not item_host or not item_port:
                    continue
                host = item_host.text()
                if not host or host.isEmpty() or host.isNull():
                    continue
                host = tool.qstring_to_string(host)
                port = item_port.text()
                port = tool.qstring_to_string(port)
                nodes.append((host, port))
            auth = tool.qstring_to_string(self.cluster_auth_line_edit.text())
            self.factory = RedisFacotry.create_cluster(nodes, auth, self.logger)
            storage = Storage()
            storage.insert(name, node_tab_current_index, nodes, auth)
        else:
            raise Exception('connect window select tab page error!')
        self.parent.tree.initialize()
        self.close()

    def on_node_table_add_row_clicked(self):
        row_count = self.node_table.row_count()
        if row_count > 0:
            last_count = row_count - 1
            last_node_host_item = self.node_table.item(last_count, 0)
            last_node_port_item = self.node_table.item(last_count, 1)
            if not last_node_host_item or not last_node_port_item:
                return
            if not last_node_host_item.text() or not last_node_port_item.text():
                return
        self.node_table.insert_row(row_count)
        item_host = self.node_table.set_item(row_count, 0, '')
        item_port = self.node_table.set_item(row_count, 1, '')
        self.node_table.set_current_item(item_host)
        self.node_table.select_row(row_count)
        self.node_table.vertical_scroll_bar().setValue(row_count)

    def on_node_table_delete_row_clicked(self):
        row = self.node_table.currentRow()
        if row > -1:
            self.node_table.removeRow(row)

    def set_client_data(self, data):
        id = data['id']
        name, auth = data['name'], data['auth']
        host, port = data['node']
        self.client_name_line_edit.setText(tool._from_utf8(name))
        self.client_host_line_edit.setText(tool._from_utf8(host))
        self.client_port_line_edit.setText(tool._from_utf8(str(port)))
        self.client_auth_line_edit.setText(tool._from_utf8(auth))

    def set_cluster_data(self, data):
        self.cluster_name_line_edit.setText(tool._from_utf8(data['name']))
        self.cluster_auth_line_edit.setText(tool._from_utf8(data['auth']))
        nodes = data['nodes']
        row_count = len(nodes)
        self.node_table.set_row_count(row_count)
        for i in range(row_count):
            host, port = nodes[i]
            self.node_table.set_item(i, 0, host)
            self.node_table.set_item(i, 1, port)


    def display(self, index):
        self.tab_widget.removeTab(index)

    def show(self):
        if not self.isVisible():
            self.setWindowModality(CoreQt.WindowModal)
            super(ConnectWindow, self).show()

    def closeEvent(self, event):
        # self.close_signal.emit()
        self.close()